package api

import (
	"log"

	"gitee.com/dingiyan/goMyAdmin/db"
	"gitee.com/dingiyan/goMyAdmin/service/dialect"
	"gitee.com/dingiyan/goMyAdmin/service/interfaces"
	"github.com/gin-gonic/gin"
)

// 获取一个数据库的表列表
func GetTableList(c *gin.Context) {
	var body struct {
		DsId         uint   `json:"dsId"`
		DatabaseName string `json:"databaseName"`
	}
	if err := c.ShouldBindJSON(&body); err != nil {
		log.Println(err)
		c.JSON(200, resError(1, "参数错误！"))
		return
	}

	serverConfig, err := db.GetServerById(body.DsId)
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(2, "查询错误！"))
		return
	}
	dbm := dialect.GetDialect(dialect.DialectMysql)

	config := serverToDatasourcesConfig(serverConfig, body.DatabaseName)

	_, err1 := dbm.ConnectDatasources(&config)
	if err1 != nil {
		log.Println(err1)
		c.JSON(200, resError(2, "连接错误！"))
		return
	}

	tables, err := dbm.GetTables()
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(3, "查询错误！"))
	}
	if tables == nil {

		tables = []interfaces.TableDetail{}
	}
	c.JSON(200, success(gin.H{
		"tables": tables,
	}))
}

// 创建一个表，表及字段
func CreateTable(c *gin.Context) {
	var body struct {
		DsId         uint                      `json:"dsId"`
		DatabaseName string                    `json:"databaseName"`
		TableName    string                    `json:"tableName"`
		Fields       []interfaces.FieldOptions `json:"fields"`
		TableArgs    map[string]any            `json:"tableArgs"`
	}
	if err := c.ShouldBindJSON(&body); err != nil {
		log.Println(err)
		c.JSON(200, resError(1, "参数错误！"))
		return
	}
	serverConfig, err := db.GetServerById(body.DsId)
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(2, "查询错误！"))
		return
	}
	dbm := dialect.GetDialect(dialect.DialectMysql)
	config := serverToDatasourcesConfig(serverConfig, body.DatabaseName)
	_, err1 := dbm.ConnectDatasources(&config)
	if err1 != nil {
		log.Println(err1)
		c.JSON(200, resError(3, "连接错误！"))
		return
	}
	err = dbm.CreateTable(body.TableName, body.Fields, body.TableArgs)
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(4, "创建表错误！"+err.Error()))
		return
	}
	c.JSON(200, success(gin.H{
		"tableName": body.TableName,
	}))
}

// 更新表，表名和字段
func UpdateTable(c *gin.Context) {
	var body struct {
		DsId         uint                      `json:"dsId"`
		DatabaseName string                    `json:"databaseName"`
		TableName    string                    `json:"tableName"`
		NewTableName string                    `json:"newTableName"` // 新表名
		NewComment   string                    `json:"newComment"`   // 新的表注释
		Fields       []interfaces.FieldOptions `json:"fields"`       // 字段更新
		TableArgs    map[string]any            `json:"tableArgs"`
	}
	if err := c.ShouldBindJSON(&body); err != nil {
		log.Println(err)
		c.JSON(200, resError(1, "参数错误！"))
		return
	}

	// 获取数据库连接配置
	serverConfig, err := db.GetServerById(body.DsId)
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(2, "查询错误！"))
		return
	}
	dbm := dialect.GetDialect(dialect.DialectMysql)
	config := serverToDatasourcesConfig(serverConfig, body.DatabaseName)
	_, err1 := dbm.ConnectDatasources(&config)
	if err1 != nil {
		log.Println(err1)
		c.JSON(200, resError(3, "连接错误！"))
		return
	}

	// 生成更新表的SQL
	alterSQL, err := dbm.GenerateAlterTableSQL(body.DatabaseName, body.TableName, body.NewTableName, body.Fields, body.TableArgs)
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(4, "获取表变更SQL错误："+err.Error()))
		return
	}

	log.Println("alterSQL:" + alterSQL)

	// 执行ALTER TABLE语句（当前被注释掉）
	// err = dbm.ExecuteSQL(alterSQL)
	// if err != nil {
	//     log.Println(err)
	//     c.JSON(200, resError(5, "执行更新表错误！"+err.Error()))
	//     return
	// }

	c.JSON(200, success(gin.H{
		"tableName": body.NewTableName,
		"alterSQL":  alterSQL,
	}))
}

// // 修改表
// func UpdateTable(c *gin.Context) {
// 	var body struct {
// 		DsId         uint                      `json:"dsId"`
// 		DatabaseName string                    `json:"databaseName"`
// 		TableName    string                    `json:"tableName"`
// 		Fields       []interfaces.FieldOptions `json:"fields"`
// 		TableArgs    map[string]any            `json:"tableArgs"`
// 	}
// 	if err := c.ShouldBindJSON(&body); err != nil {
// 		log.Println(err)
// 		c.JSON(200, resError(1, "参数错误！"))
// 		return
// 	}
// 	serverConfig, err := db.GetServerById(body.DsId)
// 	if err != nil {
// 		log.Println(err)
// 		c.JSON(200, resError(2, "查询错误！"))
// 		return
// 	}
// 	dbm := dialect.GetDialect(dialect.DialectMysql)
// 	config := serverToDatasourcesConfig(serverConfig, body.DatabaseName)
// 	_, err1 := dbm.ConnectDatasources(&config)
// 	if err1 != nil {
// 		log.Println(err1)
// 		c.JSON(200, resError(3, "连接错误！"))
// 		return
// 	}
// 	err = dbm.UpdateTable(body.TableName, body.Fields, body.TableArgs)
// 	if err != nil {
// 		log.Println(err)
// 		c.JSON(200, resError(4, "修改表错误！"))
// 		return
// 	}
// 	c.JSON(200, success(gin.H{
// 		"tableName": body.TableName,
// 	}))
// }

// 获取表字段列表
func GetTableInfo(c *gin.Context) {
	var body struct {
		DsId         uint   `json:"dsId"`
		DatabaseName string `json:"databaseName"`
		TableName    string `json:"tableName"`
	}
	if err := c.ShouldBindJSON(&body); err != nil {
		c.JSON(200, resError(1, "参数错误"+err.Error()))
		return
	}

	dbm, err := getDBManager(getUserId(c), body.DsId, body.DatabaseName)
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(2, "获取数据库管理对象出错！"+err.Error()))
		return
	}

	tableBase, fields, err := dbm.GetTableInfo(body.DatabaseName, body.TableName)
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(3, "获取表信息出错！"+err.Error()))
		return
	}

	c.JSON(200, success(map[string]any{
		"table":  tableBase,
		"fields": fields,
	}))

}

// 修改表名
func RenameTableName(c *gin.Context) {
	var body struct {
		DsId         uint   `json:"dsId"`
		DatabaseName string `json:"databaseName"`
		OldTableName string `json:"oldTableName"`
		NewTableName string `json:"newTableName"`
	}

	if err := c.ShouldBindJSON(&body); err != nil {
		c.JSON(200, resError(1, "参数错误！"))
		return
	}

	dsRecord, err := db.GetUsersServerById(getUserId(c), body.DsId)
	if err != nil {
		c.JSON(200, resError(2, "数据源不存在！"))
		return
	}
	dbm := dialect.GetDialect(dialect.DialectMysql)
	config := serverToDatasourcesConfig(dsRecord, body.DatabaseName)

	_, err1 := dbm.ConnectDatasources(&config)
	if err1 != nil {
		c.JSON(200, resError(3, "连接目标数据库失败！"))
		return
	}

	err = dbm.RenameTable(body.OldTableName, body.NewTableName)
	if err != nil {
		c.JSON(200, resError(4, "重命名表失败！"))
		return
	}
	c.JSON(200, success(true))
}

// 删除表
func DropTable(c *gin.Context) {
	var body struct {
		DsId         uint   `json:"dsId"`
		DatabaseName string `json:"databaseName"`
		TableName    string `json:"tableName"`
	}
	if err := c.ShouldBindJSON(&body); err != nil {
		log.Println(err)
		c.JSON(200, resError(1, "参数错误！"))
		return
	}

	dsRecord, err := db.GetUsersServerById(getUserId(c), body.DsId)
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(2, "数据源不存在！"))
		return
	}
	dbm := dialect.GetDialect(dialect.DialectMysql)
	config := serverToDatasourcesConfig(dsRecord, body.DatabaseName)

	_, err1 := dbm.ConnectDatasources(&config)
	if err1 != nil {
		log.Println(err1)
		c.JSON(200, resError(3, "连接目标数据库失败！"))
		return
	}
	err = dbm.DropTable(body.TableName)
	if err != nil {
		log.Println(err)
		c.JSON(200, resError(4, "删除表失败！"))
		return
	}
	c.JSON(200, success(true))

}
